#include "server.hpp"
#include <iostream>
#include <string>
#include <unordered_map>
#include<fstream>
#include<signal.h>
#include<unistd.h>

void use_manual()
{
    std::cout << "please input like: "
              << " \"./server port\" " << std::endl;
}

unordered_map<string, string> dict;

bool cutstring(string& line, string&key, string&value, string interval_type)
{
    auto pos = line.find(interval_type);
    if (pos == string::npos) 
    {
        cout << "cutstring error" << endl; 
        return false;
    }

    key = line.substr(0, pos);
    value = line.substr(pos+interval_type.size());
    return true;
}

void service_init()
{
    ifstream in("./directory.txt", std::ios::binary);
    if (!in.is_open()) {cout<< "open directory fail"<<endl; exit(0);}

    string line, key, value;
    while(getline(in, line))
    {
        if(cutstring(line, key, value, "#"))
            dict.insert(make_pair(key, value));
    }

}

void* translate_online(int fd, std::string client_ip, uint16_t client_port, std::string message)
{
    //初始化单词树
    service_init();

    //从单词树中查找用户发来的单词
    std::string re_message;
    auto it = dict.find(message);
    if (it == dict.end()) re_message = "库中暂未存放该单词";
    else re_message = it->second;

    //将查找结果返回给用户
    struct sockaddr_in to_client;
    bzero(&to_client, sizeof(to_client));
    socklen_t len = sizeof(to_client);
    to_client.sin_port = htons(client_port);
    to_client.sin_family = AF_INET;
    to_client.sin_addr.s_addr = inet_addr(client_ip.c_str());


    ssize_t check = sendto(fd, re_message.c_str(), re_message.size(), 0, (struct sockaddr*)&to_client, len);
    if (-1 == check){cout << "send re_message error" <<endl; exit(0);}
    return nullptr;
}

void update_dict(int signo)
{
    service_init();
    std::cout<< "正在更新单词库" <<endl;
}


int main(int arg, char *argc[])
{
    if (arg != 2)
    {
        use_manual();
        exit(0);
    }

    //每收到SIGINT信号，就去更新单词库
    signal(SIGINT, update_dict);
    cout << getpid() <<endl;
    server *test = new server(translate_online, atoi(argc[1]));
    test->init();
    test->start();

    delete test;

    return 0;
}